#include "CFonts.h"
#ifdef DEBUG
    CLogger* _logger = CLogger::Instance();
#endif
class CFontsCleaner
{
public:
    ~CFontsCleaner()
    {
        CFonts::Destroy();
#ifdef DEBUG
        _logger->log(LOG_LEVEL_NOTICE,"CFontsCleaner::~CFontsCleaner() : class destuctor called");
#endif

    }

}CFontsInst;

CFonts* CFonts::_instance = 0;
int CFonts::_refCount = 0;

CFonts* CFonts::Instance()
{
    if ( _instance == 0 ) // if first time ...
    {
        _instance = new CFonts(); // ... create a new 'solo' instance

#ifdef DEBUG
        _logger->log(LOG_LEVEL_NOTICE,"CFonts::Instance() : _instance created");
#endif
    }
    _refCount++; //increase reference counter

#ifdef DEBUG
    _logger->log(LOG_LEVEL_NOTICE,"CFonts::Instance() : _refCount = %d",_refCount );
#endif
    return _instance;
}

void CFonts::Release()
{
    if ( --_refCount < 1 )
    {
        Destroy();
#ifdef DEBUG
       _logger->log(LOG_LEVEL_NOTICE,"CFonts::Release()");
#endif
    }
}

void CFonts::Destroy()
{
    if ( _instance != 0 )
    {
        delete( _instance );
        _instance = 0;
#ifdef DEBUG
        _logger->log(LOG_LEVEL_NOTICE,"CFonts::Destroy() : _instance deleted" );

#endif
    }
}


void CFonts::buildFonts()
{
    m_fontTex = new CTextures();
    m_fontTex->loadTexture("font.bmp");

    float cx;    /* Holds Our X Character Coord */
    float cy;    /* Holds Our Y Character Coord */

    /* Creating 256 Display List */
    base  = glGenLists( 256 );
    /* Select Our Font Texture */
    glBindTexture( GL_TEXTURE_2D,m_fontTex->getTexture().texture );

    /* Loop Through All 256 Lists */
    for ( loop = 0; loop < 256; loop++ )
    {
        /* NOTE:
         *  BMPs are stored with the top-leftmost pixel being the
         * last byte and the bottom-rightmost pixel being the first
         * byte. So an image that is displayed as
         *    1 0
         *    0 0
         * is represented data-wise like
         *    0 0
         *    0 1
         * And because SDL_LoadBMP loads the raw data without
         * translating to how it is thought of when viewed we need
         * to start at the bottom-right corner of the data and work
         * backwards to get everything properly. So the below code has
         * been modified to reflect this. Examine how this is done and
         * how the original tutorial is done to grasp the differences.
         *
         * As a side note BMPs are also stored as BGR instead of RGB
         * and that is why we load the texture using GL_BGR. It's
         * bass-ackwards I know but whattaya gonna do?
         */

        /* X Position Of Current Character */
        cx = 1 - ( float )( loop % 16 ) / 16.0f;
        /* Y Position Of Current Character */
        cy = 1 - ( float )( loop / 16 ) / 16.0f;

        /* Start Building A List */
        glNewList( base + ( 255 - loop ), GL_COMPILE );
        /* Use A Quad For Each Character */
        glBegin( GL_QUADS );
        /* Texture Coord (Bottom Left) */
        glTexCoord2f( cx - 0.0625, cy );
        /* Vertex Coord (Bottom Left) */
        glVertex2i( 0, 0 );

        /* Texture Coord (Bottom Right) */
        glTexCoord2f( cx, cy );
        /* Vertex Coord (Bottom Right) */
        glVertex2i( 16, 0 );

        /* Texture Coord (Top Right) */
        glTexCoord2f( cx, cy - 0.0625f );
        /* Vertex Coord (Top Right) */
        glVertex2i( 16, 16 );

        /* Texture Coord (Top Left) */
        glTexCoord2f( cx - 0.0625f, cy - 0.0625f);
        /* Vertex Coord (Top Left) */
        glVertex2i( 0, 16 );
        glEnd( );

        /* Move To The Left Of The Character */
        glTranslated( 10, 0, 0 );
        glEndList( );
    }
#ifdef DEBUG
   _logger->log(LOG_LEVEL_NOTICE,"CFonts::buildFonts : Done" );
#endif

}

void CFonts::killFont()								// Delete The Font From Memory
{
    glDeleteLists(base,256);	// Delete All 256 Display Lists
    m_fontTex->Cleanup();
    delete m_fontTex;
#ifdef DEBUG
    _logger->log(LOG_LEVEL_NOTICE,"CFonts::killFonts : Done" );
#endif

}

void CFonts::glPrint(GLint x, GLint y, char *string, int set)				// Where The Printing Happens
{
    if (set>1)								// Is set Greater Than One?
    {
        set=1;								// If So, Make Set Equal One
    }
    glBindTexture(GL_TEXTURE_2D,m_fontTex->getTexture().texture);				// Select Our Font Texture
    //glTexEnvf(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_REPLACE);
    //glDisable(GL_DEPTH_TEST);						// Disables Depth Testing
    glMatrixMode(GL_PROJECTION);						// Select The Projection Matrix
    glPushMatrix();								// Store The Projection Matrix
    glLoadIdentity();							// Reset The Projection Matrix
    glOrtho(0,800,0,600,-1,1);						// Set Up An Ortho Screen
    //gluOrtho2D(0.0f,800,600,0.0f); /* setting view to 2d orthogonal mode */
    glMatrixMode(GL_MODELVIEW);						// Select The Modelview Matrix
    glPushMatrix();								// Store The Modelview Matrix
    glLoadIdentity();							// Reset The Modelview Matrix
    glTranslated(x,y,0);							// Position The Text (0,0 - Bottom Left)
    glListBase(base-32+(128*set));						// Choose The Font Set (0 or 1)
    glCallLists(strlen(string),GL_BYTE,string);			// Write The Text To The Screen
    glMatrixMode(GL_PROJECTION);						// Select The Projection Matrix
    glPopMatrix();								// Restore The Old Projection Matrix
    glMatrixMode(GL_MODELVIEW);						// Select The Modelview Matrix
    glPopMatrix();								// Restore The Old Projection Matrix
    //glEnable(GL_DEPTH_TEST);						// Enables Depth Testing
}


